class Scene extends egret.Sprite{

	private frame:number = 0;
	private bg:egret.Shape;
	private snake:Snake;
	private snakeSpeed:number;
	private unitGenSpeed:number;
	private isOver:boolean = true;
	private dir:number = 3;
	private foodList:Array<Food> = [];

	constructor(){
		super();
		this.initBg();
		this.initSnake();
		this.initKeyEvent();
		this.addEventListener(egret.Event.ENTER_FRAME,this.onEnterFrame,this);
		this.start();
	}

	private initKeyEvent(){
		let d = this;
		document.onkeydown = function(e:any){
			e = e||event;
			let key:number = e.keyCode||e.which||e.charCode;
			console.log(key);
			if(d.isOver){
				if(isPress(key,KEY_RESTART)){
					d.start();
				}
			}
			if(isPress(key,KEY_LEFT)){
				d.setDir(Snake.LEFT);
			}else if(isPress(key,KEY_RIGHT)){
				d.setDir(Snake.RIGHT);
			}else if(isPress(key,KEY_UP)){
				d.setDir(Snake.UP);
			}else if(isPress(key,KEY_DOWN)){
				d.setDir(Snake.DOWN);
			}
		}
	}
	
	private setDir(d:number){
		if(Snake.isAgainst(d,this.snake.curDir)){
			return;
		  }
		this.dir = d;
	}

	private initBg():void{
		this.bg = new egret.Shape();
		this.addChild(this.bg);
		this.bg.graphics.lineStyle(1,0xcccccc);
		for(let i:number = 0; i<GRID_ROWS; i++){
			this.drawLine(i);
		}
		for(let j:number = 0; j<GRID_COLUMNS; j++){
			this.drawLine(j,true);
		}
		this.drawLine(GRID_COLUMNS,true);
		this.bg.graphics.endFill();
	}

	private drawLine(index:number,isV:boolean = false):void{
		if(!isV){
			this.bg.graphics.moveTo(0,index * GRID_SIZE);
			this.bg.graphics.lineTo(GRID_COLUMNS * GRID_SIZE,index * GRID_SIZE);
		}else{
			this.bg.graphics.moveTo(index * GRID_SIZE,0);
			this.bg.graphics.lineTo(index * GRID_SIZE,(GRID_ROWS - 1) * GRID_SIZE);
		}
	}

	private initSnake():void{
		this.snake = new Snake(3,Snake.DOWN);
		this.addChild(this.snake);
	}

	private onEnterFrame(e:egret.Event):void{
		if(this.isOver){
			return;
		}
		if(this.frame % this.snakeSpeed ==  0){
			this.snakeMove(); 
		}if(this.frame % this.unitGenSpeed == 0){
			this.unitRefresh();
		}
		this.frame ++;
	}

	private start():void{
		this.snakeSpeed = INITIAL_SNAKE_SPEED;
		this.unitGenSpeed = INITIAL_UNIT_SPEED;
		this.snake.reset(3,Snake.DOWN);
		this.isOver = false;

		console.log("well");
	}


	private snakeMove():void{
		if(this.snake.gx >= GRID_COLUMNS || 
		  this.snake.gx < 0 || 
		  this.snake.gy >= GRID_ROWS - 1 || 
		  this.snake.gy < 0 ||
		  this.snake.hitSelf()){
			this.gameOver();
			return;
		}
		let addFlag:boolean = false;
		for(let i:number = this.foodList.length - 1;i >= 0;i--){
			let food:Food = this.foodList[i];
			if(food.gx == this.snake.gx && this.snake.gy == food.gy){
				food.destroy();
				this.foodList.splice(i,1);
				addFlag = true;
				break;
			}
		}
		if(addFlag){
			this.snake.add();
		}
		this.snake.move(this.dir);
	}

	private unitRefresh():void{
		for(let i:number = this.foodList.length - 1;i >= 0;i--){
			let food:Food = this.foodList[i];
			if(food.update()){
				this.foodList.splice(i,1);
			}
		}
		this.tryAddFood();	
		//this.createUnit();
	}

	private tryAddFood(){
		if(this.foodList.length < MAX_FOOD_IN_SCENE){
			let food:Food = Food.create();
			let gx:number = Math.floor(Math.random() * (GRID_COLUMNS - 1));
			let gy:number = Math.floor(Math.random() * (GRID_ROWS - 1));
			food.setPos(gx,gy);
			this.addChild(food);
			this.foodList.push(food);
		}
	}

	private gameOver(){
		this.isOver = true;
	}

}

